home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Apple II Magazines (DO)
/
Peeker Nr. 15 (1986)(Verlag, Dr. Alfred Huethig)(DE).zip
/
Peeker Nr. 15 (1986)(Verlag, Dr. Alfred Huethig)(DE).do
/
T.MAKESUB.s
< prev
Wrap
Text File
|
1996-12-24
|
18KB
|
605 lines
*-----------------------------*
* MAKESUB *
* von Arne Sch{pers, 1985 *
*-----------------------------*
*
PTR EQU $06 ; ($07)
PROMPT EQU $33 ; f}r GETLIN
COUTV EQU $36 ; I/O-Vektoren
*
PATH EQU $280 ; interner Pathname
*
RESTART EQU $3D3 ; (Pro)DOS-Warmstart
*
* Monitor-Routinen:
*
HOME EQU $FC58
GETKEY EQU $FD0C ; GET ein Zeichen
GETLIN EQU $FD6F ; GET eine Zeile
PRBYTE EQU $FDDA ; Print Akku in Hex
COUT EQU $FDED ; PRINT
*
ORG $803
*
LDX #03
DISCONN LDA $BE30,X ; BASIC.SYSTEM ab!
STA COUTV,X
DEX
BPL DISCONN
*
JSR HOME
LDX #0
JSR PRT1 ; "Erstellung von..."
INX
JSR PRTMSG ; "Eingabe Filename: "
LDA #$BA
STA PROMPT ; ":"
JSR GETLIN
JSR SETPATH ; Path + PREFIX => $280
GETNUM LDX #GETLEN-MSGS
JSR PRTMSG ; "Block-Anzahl: "
JSR GETLIN
JSR SETNUM ; ASCII => Hex
BCS GETNUM ; illegale Zeichen: Loop
LDX #START-MSGS
JSR PRTMSG ; "<CR>=Start, <ESC>..."
GETSTART JSR GETKEY
CMP #$8D ; <CR>?
BEQ GOTSTART
CMP #$9B ; <ESC>?
BNE GETSTART
JMP EXIT ; Abbruch
*
GOTSTART LDA BLWANT+1 ; Anzahl gew}nschte
LDY BLWANT ; Blocks =>
STA BLNEED+1 ; Anzahl ben|tigte
STY BLNEED ; Blocks
LSR EXISTS ; Flag zur}ck
JSR TSTFILE ; sucht das SubDIR via MLI
BEQ TSTROOM ; nicht gefunden
CMP #$00 ; SubDIR existiert?
BEQ TSTTYPE
JMP NOVOL ; nein, PATH NOT FOUND
TSTTYPE LDA #$80
STA EXISTS ; Flag setzen
LDA STYPE ; aus TSTFILE, FILE INFO
CMP #$0D ; ist SubDIR?
BEQ SETNEED
JMP BADTYPE ; "FILE TYPE MISMATCH"
SETNEED LDA BLNEED ; SubDIR existiert:
SEC ; die Anzahl der
SBC BLUSED ; ben|tigten Blocks
STA BLNEED ; wird entsprechend
LDA BLNEED+1 ; heruntergesetzt
SBC BLUSED+1
STA BLNEED+1
BCC TOOLONG ; USED > NEEDED!
ORA BLNEED ; zus{tzliche Blocks
BNE TSTROOM ; = 00 00?
JMP DONE ; nichts zu tun...
TOOLONG JMP BADLEN ; "SET EOF?"
*
TSTROOM JSR GETROOM ; GET F'INFO VolDIR
BCS ROOMOK ; und Test BLOCKS_FREE
JMP NOROOM ; "VOLUME FULL"
*
ROOMOK LDA $BF30 ; "last used Unit"
STA RWUNIT ; f}r BLOCKREAD/WRITE
BIT EXISTS
BMI SETENTRY
JSR MAKEDIR ; neues DIR CREATE
JSR DECNEED ; BLOCKS_NEEDED-1
BNE SETENTRY ; bleiben noch Blocks
JMP DONE ; fertig
*
SETENTRY JSR GETFILE ; sucht SubDIR und setzt
LDY #$13 ; PTR auf File-Eintrag
LDA BLWANT ; f}r das SubDIR
STA (PTR),Y
INY
LDA BLWANT+1 ; BLOCKS_USED im
STA (PTR),Y ; File-Eintrag
INY
INY
LDA BLWANT ; EOF des SubDIR
ASL ; => BLOCKS * $200
STA (PTR),Y ; und wird gesetzt
INY
LDA BLWANT+1
ROL
STA (PTR),Y ; EOF, h|chstes Byte
JSR MLIWRITE ; schreibt DIR zur}ck
*
JSR SETBLOCK1 ; setzt 1.Block aus Eintrag
GETDEND JSR RDBLOCK ; liest ersten/n{chsten
LDA DIRBUF+2 ; Block des SubDIR
TAY ; nach DIRBUF
ORA DIRBUF+3 ; FORWARD REF = 00 00?
BEQ APPEND ; ja, SubDIR jetzt zu Ende
LDA DIRBUF+3
JMP GETDEND ; geht noch weiter
*
APPEND JSR READVBM ; 1.VBM-Block nach VBMBUF
BEQ SETLINK ; "always"
*
NEWBLOCK LDA RWBLOCK+1 ; Vorbereiten eines
LDY RWBLOCK ; neuen SubDIR-Blocks:
STA DIRBUF+1 ; die Nummer des zuletzt
STY DIRBUF+0 ; gelesenen Blocks wird
LDA DIRBUF+3 ; als BACKWARD REF,
LDY DIRBUF+2 ; die alte FORWARD REF
STA RWBLOCK+1 ; als n{chste Blocknummer
STY RWBLOCK ; f}r WRITE eingetragen
*
LDX #0 ; danach wird der
TXA ; neue Block gel|scht,
CLRBLOCK STA DIRBUF+2,X
STA DIRBUF+$100,X
INX ; bis auf die Bytes 00
BNE CLRBLOCK ; und 01 (BACKWARD REF)
*
NXTLINK JSR DECNEED ; BLNEED-1
BEQ LINK00 ; => letzter Block
SETLINK JSR GNBLOCK ; nein, n{chster Block
STA DIRBUF+3 ; wird belegt und als
STY DIRBUF+2 ; FOWARD REF eingetragen
LINK00 JSR MLIWRITE ; schreibt den Block
JSR TSTNEED ; noch weitere Blocks?
BNE NEWBLOCK
JSR WRITEVBM ; VBM zur}ckschreiben
*
DONE LDX #DONMSG-MSGS
JSR PRTMSG ; "- Fertig."
JMP EXIT
*
DECNEED LDA BLNEED ; setzt BLOCKS_NEEDED
SEC ; um eins herunter und
SBC #01 ; pr}ft, ob noch
STA BLNEED ; weitere Blocks
BCS TSTNEED ; anzuh{ngen sind
DEC BLNEED+1
TSTNEED LDA BLNEED+1
ORA BLNEED ; beide auf 00?
RTS
*
EXISTS DS 1 ; <$80, wenn SubDIR neu
*
BLWANT DS 2 ; BLOCKS_WANTED
BLNEED DS 2 ; BLOCKS_NEEDED
*
************************
*
SETPATH LDX #00
LDA $0200,X
AND #$7F ; Start des Path
CMP #'/' ; mit "/"?
BEQ GOTPATH
JSR $BF00 ; ansonsten
DFB $C7 ; GET PREFIX
DA PFXLIST
BEQ GOTPFX ; "always"!
PFXLIST DFB 01 ; 1 Parameter
DA PATH-1 ; Ziel: $027F
*
GOTPFX LDX PATH-1 ; Gesamtl{nge
GOTPATH LDY #00
COPYPATH LDA $0200,Y ; Path wird von $200
AND #$7F ; nach PATH kopiert
CMP #$0D ; Path-Ende?
BEQ PATHSET
CMP #$60 ; Kleinbuchstabe?
BCC ISUC
AND #$5F ; Umwandlung in gro~
ISUC STA PATH,X ; bzw. an das PREFIX
INX ; angeh{ngt
INY
BNE COPYPATH
PATHSET STX PATH-1 ; Gesamtl{nge
RTS
*
SETNUM LDX #00 ; wandelt ASCII-Hexstring
STX BLWANT ; in BLOCKS_WANTED um
STX BLWANT+1
NXTNUM LDA $0200,X
CMP #$8D ; <CR>?
BEQ NUMSET ; Zahl zu Ende
CMP #$E0
BCC ISCAPS
AND #$DF ; Umwandlung in gro~
ISCAPS LDY #04
SEC
SBC #$B0 ; minus "0"
BCC BADNUM ; keine Zahl
CMP #$0A
BCC ISNUM ; "0".."9"
SBC #$07
CMP #$10 ; "A".."F"?
BCS BADNUM ; nein
ISNUM ASL BLWANT ; alte Zahl * 16
ROL BLWANT+1
DEY
BNE ISNUM
ORA BLWANT ; neue Zahl dazu
STA BLWANT
INX
BNE NXTNUM
*
NUMSET LDA BLWANT
ORA BLWANT+1 ; Zahl > 00 00?
BEQ BADNUM
CLC
RTS
BADNUM SEC
RTS
*
TSTFILE JSR $BF00 ; GET FILE INFO
DFB $C4 ; f}r das neue SubDIR
DA INFOLIST
CMP #$46 ; FILE NOT FOUND?
BEQ TSTEND
CMP #$00 ; File gefunden?
BEQ TSTZ ; ja, ist auch o.k.
SBC #$44 ; Fehler im
CMP #$02 ; Bereich $44-45?
BCC TSTZ ; ja, PATH NOT FOUND
ADC #$43 ; => ERR# f}r MLIERR
JMP MLIERR
TSTZ LDY #$FF ; l|scht Z-Flag
TSTEND RTS
*
GETROOM LDA PATH-1 ; Gesamtl{nge des
PHA ; Path speichern
LDX #00
GETVDIR INX ; und nur das VolDIR
LDA PATH,X ; herausholen
CMP #'/' ; Ende erster Name?
BNE GETVDIR
STX PATH-1 ; nur VolDIR-Name
JSR $BF00
DFB $C4 ; GET FILE INFO
DA INFOLIST ; f}r VolDIR
BEQ GOTVDIR
JMP MLIERR ; "MLI-Fehler: $xx"
GOTVDIR PLA
STA PATH-1 ; RESTORE des Path
LDA AUXRTN ; TOTAL_BLOCKS auf
SEC ; dem Volume minus
SBC BLUSED ; belegte Blocks auf
TAX ; dem Volume ergibt
LDA AUXRTN+1 ; BLOCKS_FREE
SBC BLUSED+1
CMP BLNEED+1 ; ben|tigte Blocks
BCC ROOMGOT ; kein Platz!
BNE ROOMGOT ; o.k.
CPX BLNEED
ROOMGOT RTS ; C = 0, => kein Platz
*
INFOLIST DFB $0A ; 10 Parameter
DA PATH-1 ; Pathname
DS 2 ; ACCESS, File Type
AUXRTN DS 2 ; AUX_INFO
STYPE DS 1 ; Storage Type
BLUSED DS 2 ; BLOCKS_USED
DS 8 ; DATE & TIME
*
MAKEDIR JSR $BF00
DFB $C0 ; CREATE des SubDIR
DA CRLIST
BEQ MKDONE
JMP MLIERR
MKDONE RTS
*
CRLIST DFB $07 ; 7 Parameter
DA PATH-1 ; Pathname
DFB $C3 ; ACCESS
DFB $0F ; File Type: DIR
DA $0000 ; AUX_TYPE
DFB $0D ; Storage Type: SubDIR
DFB 0,0,0,0 ; DATE & TIME
*
GETFILE LDX PATH-1 ; Gesamtl{nge
RPL1 LDY #$FF
RPL2 DEX ; der Path wird von
BMI SCANDIRS ; "/xxx/yyyy" in
INY ; die Form:
LDA PATH,X ; <03>xxx<04>yyyy
CMP #'/' ; }berf}hrt, d.h.
BNE RPL2 ; alle "/" im Path
TYA ; werden durch L{ngen-
STA PATH,X ; bytes ersetzt
BNE RPL1
*
SCANDIRS LDX PATH+0 ; Start mit dem zweiten
INX ; Namen im Path
STX PATHIDX ; (nach dem VolDIR)
LDY #$02 ; und dem ersten Block
LDA #$00 ; des VolDIR
JSR RDBLOCK ; READ Block $0002
LDA DIRBUF+$28
LDY DIRBUF+$27
STA VBMNO+1 ; Blocknummer des
STY VBMNO ; ersten VBM-Blocks
*
DIRSET LDX #$80 ; Flag: erster Block
STX BLOCK1 ; wird gesetzt
DOSCAN JSR SCAN ; sucht nach Path-Namen
BCC NXTDIR ; dieser Name gefunden
LDA DIRBUF+3 ; FORWARD REF: Setzen
LDY DIRBUF+2 ; des n{chsten DIR-Blocks
JSR RDBLOCK ; liest den Block
BEQ DOSCAN ; "always"
*
NXTDIR LDX PATHIDX ; war dieser Name
TXA ; der letzte im Path?
SEC
ADC PATH,X ; Index auf n{chsten Namen
CMP PATH-1 ; = Gesamtl{nge?
BCS GOTFILE
STA PATHIDX ; nein, n{chster Name
JSR SETBLOCK1 ; im Path. Der erste Block
JSR RDBLOCK ; des hier gefundenen DIR
BEQ DIRSET ; wird gelesen => Loop
GOTFILE RTS ; mit PTR auf neues SubDIR
*
SCAN LDA #>DIRBUF ; sucht einen DIR-Block
STA PTR+1 ; nach einem Namen
LDA #$04 ; im Path als File-Eintrag ab
CLC
BIT BLOCK1 ; erster Block dieses DIR?
BPL NOT1ST ; nein
LDY DIRBUF+$24
STY ENUMBER ; Eintr{ge pro Block
LDY DIRBUF+$23
STY ELENGTH ; L{nge eines Eintrags
ADC ELENGTH ; HEADER }berspringen
LSR BLOCK1 ; Flag zur}ck
*
NOT1ST LDY ENUMBER ; Eintr{ge/Block
STY ECOUNT ; Herunterz{hler
*
NXTENTRY STA PTR
LDA PTR+1 ; PTR auf ersten/
ADC #00 ; n{chsten Eintrag
STA PTR+1 ; im Block
JSR CMPNAME ; vergleicht Eintrag & Path
BCC GOTNAME ; gefunden!
DEC ECOUNT ; noch Eintr{ge }brig?
BEQ NOTFOUND ; nein, Block-Ende
LDA PTR
CLC ; PTR auf n{chsten Eintrag
ADC ELENGTH
JMP NXTENTRY
*
NOTFOUND SEC
GOTNAME RTS
*
CMPNAME LDY #00
LDX PATHIDX ; Index zum momentanen Namen
LDA (PTR),Y ; 1.Byte v. File-Eintrag
AND #$0F ; => Namensl{nge
CMP PATH,X ; = Path-Name?
BNE NOTSAME
TAY
CLC
ADC PATHIDX ; Start des Vergleichs
TAX ; von hinten
CMP1 LDA (PTR),Y
CMP PATH,X
BNE NOTSAME
DEX
DEY
BNE CMP1
CLC ; Namen sind gleich
RTS
NOTSAME SEC
RTS
*
SETBLOCK1 LDY #$12 ; holt die Nummer
LDA (PTR),Y ; des ersten Blocks
PHA ; im File aus dem
DEY ; File-Eintrag nach
LDA (PTR),Y ; A-Y
TAY
PLA
RTS
*
PATHIDX DS 1 ; Index in PATH
BLOCK1 DS 1 ; Flag: $80, wenn 1.DIR-Block
ENUMBER DS 1 ; Anzahl Eintr{ge/DIR-Block
ELENGTH DS 1 ; L{nge eines Eintrags
ECOUNT DS 1 ; Herunterz{hler im DIR-Block
*
RDBLOCK STA RWBLOCK+1 ; Aufruf mit
STY RWBLOCK ; Blocknr. in A-Y
JSR $BF00
DFB $80 ; READ BLOCK
DA RWLIST
BEQ RWDONE
JMP MLIERR ; "MLI-Fehler: $xx"
*
RWLIST DFB $03 ; 3 Parameter
RWUNIT DS 1 ; Unit-Nummer
DA DIRBUF ; Ziel/Quelle: DIRBUF
RWBLOCK DS 2 ; Blocknummer
*
MLIWRITE JSR $BF00
DFB $81 ; WRITE BLOCK
DA RWLIST ; Blocknr. ist gesetzt!
BEQ RWDONE
JMP MLIERR ; "MLI-Fehler: $xx"
RWDONE RTS
*
READVBM LDA #00
STA EXTENT ; VBM-Block Nummer 1
STA ALTERED ; "unver{ndert"
*
GETVBM LDA VBMNO ; Nummer 1.VBM-Block
CLC
ADC EXTENT ; "x-ter" VBM-Block
STA VBLOCK
LDA VBMNO+1
ADC #00
STA VBLOCK+1 ; Blocknummer Hi
LDA RWUNIT
STA VUNIT ; Unit-Nummer
*
JSR $BF00
DFB $80 ; READ BLOCK
DA VBMLIST
BEQ GOTVBM
JMP MLIERR ; "MLI-Fehler: $xx"
*
WRITEVBM BIT ALTERED ; "ver{ndert"?
BPL GOTVBM ; nein, kein REWRITE
LSR ALTERED ; sonst Flag zur}ck
JSR $BF00
DFB $81 ; BLOCK WRITE
DA VBMLIST
BEQ GOTVBM
JMP MLIERR ; "MLI-Fehler: $xx"
*
GOTVBM RTS
*
VBMLIST DFB $03 ; 3 Parameter
VUNIT DS 1 ; Unit-Nummer
DA VBMBUF ; Ziel/Quelle: VBMBUF
VBLOCK DS 2 ; Blocknummer
*
EXTENT DS 1 ; "x-ter" VBM-Block
PAGE DS 1 ; Seite im VBM-Block
INBYTE DS 1 ; Index in einem VBM-Byte
*
ALTERED DS 1 ; $80: VBM-Block ver{ndert
VBMNO DS 2 ; Blocknr. 1. VBM-Block
*
GNBLOCK LDY #00 ; belegt den n{chsten
STY PAGE ; freien Block und returnt
STY PTR ; Blocknr. in A-Y
LDA #>VBMBUF ; Adresse Hi
STA PTR+1
*
TSTBYTE LDA (PTR),Y
BNE GETBIT ; mindestens 1 Block frei!
INY
BNE TSTBYTE
INC PTR+1
INC PAGE ; Speicherseite-Z{hler,
LDA PAGE ; wird f}r Bestimmung der
CMP #02 ; Blocknr. ben|tigt
BCC TSTBYTE
*
JSR WRITEVBM ; REWRITE dieses VBM-Blocks
INC EXTENT ; n{chster VBM-Block
JSR READVBM
BEQ GNBLOCK ; => Loop
*
GETBIT LDX #0 ; holt ein gesetztes
GETB1 ROL ; Bit aus dem Akku
BCS GOTBIT ; und z{hlt dabei mit
INX
BNE GETB1
GOTBIT STX INBYTE ; 0..7: Nummer des Bits
CLC ; dieses Bit l|schen!
GOTB1 ROR ; und Restore des Akku
DEX
BPL GOTB1
*
STA (PTR),Y ; Block belegt in VBM
LDA #$80 ; dieser VBM-Block mu~
STA ALTERED ; zur}ckgeschrieben werden
*
LDA EXTENT ; "x-ter" VBM-Block:
ASL ; Blocknummer * $1000
ORA PAGE ; "Seite" darin:
STA BLOCKHI ; Blocknummer * $800
TYA ; Index in der Seite:
LDY #03 ; Blocknummer * $08
X8 ASL
ROL BLOCKHI ; insgesamt * 8
DEY
BNE X8
ORA INBYTE ; + 0...7
TAY ; Blocknummer Low
LDA BLOCKHI
RTS
*
BLOCKHI DS 1 ; Scratch: Blocknr. Hi
*
************
*---EXIT---*
************
*
EXIT LDA #$8D
JSR COUT ; 2mal <CR>
JSR COUT
LDA #$00
STA $48 ; ???
JMP RESTART ; DOS-Warmstart
*
MLIERR PHA ; Fehlernummer
LDX #DSKERR-MSGS
JSR PRTERR ; "MLI-Fehler: $"
PLA
JSR PRBYTE ; ERR# in Hex
JMP EXIT
*
BADTYPE LDX #BADTXT-MSGS
BNE SETERR ; "FILE TYPE MISMATCH"
*
BADLEN LDX #LENTXT-MSGS
BNE SETERR ; "Verk}rzung ..."
*
NOVOL LDX #BADVOL-MSGS
BNE SETERR ; "PATH NOT FOUND"
*
NOROOM LDX #VOLFULL-MSGS
*
SETERR JSR PRTERR
JMP EXIT
*
PRTERR LDA #$87 ; BELL
JSR COUT
*
PRTMSG LDA #$8D ; 2mal <CR>
JSR COUT
JSR COUT
PRT1 LDA MSGS,X
BEQ PRDONE ; <00>: Text-Ende
ORA #$80
JSR COUT
INX
BNE PRT1 ; "always"
PRDONE RTS
*
MSGS ASC 'Erstellung von Subdirectories'
DFB $8D,$8D
ASC 'mit definierter Block-Anzahl'
DFB $8D,$8D,00
ASC 'Eingabe Filename: '
DFB 00
*
GETLEN ASC 'Block-Anzahl (Hex): '
DFB 00
*
START ASC '<CR>=Start <ESC>=Abbruch'
DFB 00
*
DONMSG ASC '- Fertig.'
DFB 00
*
DSKERR ASC 'MLI-Fehler: $'
DFB 00
BADTXT ASC 'FILE TYPE MISMATCH'
DFB 00
LENTXT ASC 'Verk}rzung nicht m|glich!'
DFB 00
BADVOL ASC 'PATH NOT FOUND'
DFB 00
VOLFULL ASC 'VOLUME FULL'
DFB 00
*
DIRBUF EQU $1000
VBMBUF EQU DIRBUF+$200
LST OFF